package com.heisen.uua.service;

import com.heisen.base.utils.GsonUtils;
import com.heisen.redis.utils.RedisUtils;
import com.heisen.uua.constant.UuaConstant;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.oauth2.common.exceptions.InvalidClientException;
import org.springframework.security.oauth2.provider.ClientDetails;
import org.springframework.security.oauth2.provider.client.BaseClientDetails;
import org.springframework.security.oauth2.provider.client.JdbcClientDetailsService;
import org.springframework.stereotype.Service;

import javax.sql.DataSource;


/**
 *  客户端优化  先从reids中读取   没有在从数据库中都客户端的信息
 */
@Service
@Slf4j
public class RedisClientDetailsService extends JdbcClientDetailsService {

    @Autowired
    RedisUtils redisUtils;
    public RedisClientDetailsService(DataSource dataSource) {
        super(dataSource);
    }


    /**
     *  读取客户端的信息
     * @param clientId The client id.
     * @return
     * @throws InvalidClientException
     */
    @Override
    public ClientDetails loadClientByClientId(String clientId) throws InvalidClientException {

        ClientDetails clientDetails = null;

        // 先从redis获取
        String value = (String) redisUtils.getForKey( UuaConstant.RedisPrefix.CLIENTID_PREFIX+clientId);
        if (StringUtils.isBlank(value)) {
            clientDetails = cacheAndGetClient(clientId);
        } else {

            clientDetails =  GsonUtils.toBean(value, BaseClientDetails.class);
        }

        return clientDetails;

    }


    /**
     * 缓存client并返回client
     *
     * @param clientId
     */
    private ClientDetails cacheAndGetClient(String clientId) {
        // 从数据库读取
        ClientDetails clientDetails = super.loadClientByClientId(clientId);
        if (clientDetails != null) {// 写入redis缓存
            redisUtils.setForObj(UuaConstant.RedisPrefix.CLIENTID_PREFIX+clientId, GsonUtils.toJson(clientDetails));
        }
        return clientDetails;
    }
}

